/*
 * To change this template, choose Tools | Templates
 * and open the template in the editor.
 */

package utilidades;

import java.io.IOException;
import java.io.Serializable;
import java.net.URL;
import java.util.*;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

/**
 * Clase para cargar y almacenar las propiedades
 * especificadas en los diferentes archivos properties
 * @author williandv
 */
public class Propiedades implements Serializable{
    
    /**
     * Creates a new instance of NsApplicationProperties
     * Se declara private para que solamente se tenga una instancia de este objeto a nivel de aplicacion.
     * Se debe utilizar getInstance para obtener la instancia del objeto.
     */
    
     private static Propiedades currentApplicationProperties = null;
   
    /**
     * Map con las propiedades cargadas para la autenticacion
     */
    private Map<String, String> authenticationProperties = null;      
    private Map<String, String> mensagesProperties = null;
    private Map<String, String> jdbcProperties = null;
    private Map<String, String> mailProperties = null;
   
   
    /**
     * Set con el contenido excluido de ser examinado para permisos
     */
    private Set<String> nsExcludedContent = new HashSet<String>();
      
    public Propiedades(){
        this.init();
    }
    
    /**
     * Implementacion del patron de diseno Singleton
     * @return Instancia de esta clase
     */
    public static Propiedades getInstance() {
        if ( currentApplicationProperties == null ) {
            currentApplicationProperties = new Propiedades();
        }
        return currentApplicationProperties;
    }
   
    /**
     * Inicializacion de los elementos de la clase
     */
    public void init() {
        if ( this.authenticationProperties == null) {
            // ////////////////////////////////////////////////////////////////////////////////////////
            //se debe establecer cómo manejaremos la autenticación.
            // Leer configuracion para autenticacion, 
            //this.authenticationProperties = readProperties("/authentication.properties");
        }
               
        if ( this.mensagesProperties == null) {
            // Leer configuracion de conexiones a DB
            this.mensagesProperties = readProperties("..\\..\\..\\mensages.properties");
        }
        if ( this.jdbcProperties == null) {
            // Leer configuracion de conexiones a DB
            this.jdbcProperties = readProperties("..\\..\\..\\ConexionProp.properties");
        }
      /* if ( this.mailProperties == null) {
            // Leer configuracion de conexiones a DB
            this.mailProperties = readProperties("..\\..\\..\\mail.properties");
        }*/
         
           //pendiente para cuando se haga la autenticación    
        // Configurar contenido anonimo.
//        if ( this.authenticationProperties.get("excludedContent") != null ) {
//            String[] ecPatterns = this.authenticationProperties.get("excludedContent").split(",");
//            if ( ecPatterns != null ) {
//                for ( int i=0; i<ecPatterns.length; i++ ) {
//                    if ( ecPatterns[i] != null ) {
//                        ecPatterns[i] = ecPatterns[i].trim();
//                        if ( ecPatterns[i].length() > 0 ) {
//                            ecPatterns[i] = ecPatterns[i].replace(".", "\\.").replace("*", "(.*)");
//                            String excludePattern = "^"+ecPatterns[i]+"$";
//                            this.nsExcludedContent.add(excludePattern);
//                        }
//                    }
//                }
//            }
//        }
    }   
      
    /**
     * Metodo para determinar si una path que el usuario esta intentando acceder
     * esta excluido de ser examinado por los permisos (imagenes, pagina de login, css, js)
     * @param path Ruta que se intenta acceder
     * @return true, si no deber ser examinada la autotizacion sobre la ruta
     * false, si la ruta debe ser examinada para determinar si el usuario tiene permisos
     */
    public boolean isExcludedContent( String path ) {
        if ( path != null ) {
            Iterator<String> it = nsExcludedContent.iterator();
            while ( it.hasNext() ) {
                String key = it.next();
                Pattern pattern = Pattern.compile(key, Pattern.CASE_INSENSITIVE);
                Matcher matcher = pattern.matcher(path);
                if ( matcher.matches() ) {
                    return true;
                }
            }
        }
        return false;
    }
   
    /**
     * Lee las propiedades cargadas en el archivo authentication.properties
     * @return
     */
    private Map<String, String> readProperties(String path) {
        Map<String, String> applicationProperties = new HashMap<String, String>();
        Properties properties = new Properties();
        URL p = this.getClass().getResource(path);
        System.out.println(p.getPath());
        try {
            properties.load(this.getClass().getResourceAsStream(path));
            for (Enumeration en = properties.keys(); en.hasMoreElements(); ) {
                String key = (String)en.nextElement();
                applicationProperties.put(key, properties.getProperty(key));
            }
        } catch (IOException ex) {
            ex.printStackTrace();
        }
        return applicationProperties;
    }
      
   
    /**
     * Map con las propiedades cargadas
     * @return Propiedades cargadas
     */
    public Map<String, String> getNsApplicationProperties() {
        return this.authenticationProperties;
    }
   
       
    /**
     * Metodo para descargar los objetos de memoria
     */
    public void destroy() {
        this.authenticationProperties = null;
        this.nsExcludedContent = null;
        this.mensagesProperties = null;
    }
    
    public String getMensagesProperties(String propertyName) {
        return mensagesProperties.get(propertyName);
    }
    
    public String getJdbcProperties(String propertyName) {
        return jdbcProperties.get(propertyName);
    }
    
    /*public String getMailProperties(String propertyName) {
        return mailProperties.get(propertyName);
    }*/
    
    public static void main(String[] args) {
        getInstance();
        for(String s: getInstance().mensagesProperties.values()){
            System.out.println("valor :  "+s);
        }
    }

}
